<?php

class EntidadeBase
{

    public $Id;

    public function __construct()
    {
        $this->Id = 0;
    }

    public function ObterPorId($Id)
    {
        $entidades = $this->ObterLista("Id = " . $Id);
        return $entidades[0];
    }

    public function ObterPrimeiro($where = "")
    {
        $itens = $this->ObterLista($where);

        if ($itens == NULL || count($itens) == 0)
            return NULL;

        return $itens[0];
    }

    public function ObterLista($where = "")
    {
        $sql = $this->MontarSelect($where);
        $registros = $this->ObterRegistrosDoBanco($sql);
        $entidades = $this->ConverterRegistros($registros);

        return $entidades;
    }

    public function Count($where = "")
    {
        $sql = $this->MontarCount($where);
        $registros = $this->ObterRegistrosDoBanco($sql);

        while ($registro = mysql_fetch_array($registros))
        {
            return $registro[0];
        }

        return 0;
    }

    public function Somar($campo, $where = "")
    {
        $sql = $this->MontarSoma($campo, $where);
        $registros = $this->ObterRegistrosDoBanco($sql);

        while ($registro = mysql_fetch_array($registros))
        {
            return $registro[0];
        }

        return 0;
    }

    public function Salvar($entidadeBase)
    {
        if ($entidadeBase->Id == 0)
            $this->Insert($entidadeBase);
        else
            $this->Update($entidadeBase);
    }

    public function DeletarPorId($Id)
    {
        include_once "mysqlexecuta.php";
        include "mysqlconecta.php";

        $sql = $this->MontarDelete("Id = $Id");
        mysqlexecuta($id, $sql);
    }

    private function MontarSelect($where = "", $order = "2, 1")
    {
        $reflection = new ReflectionClass($this);

        $sql = "select * from " . $reflection->name;

        if ($where != "")
            $sql = $sql . " where " . $where;

        $sql = $sql . " order by $order;";

        return $sql;
    }

    private function MontarCount($where = "")
    {
        $reflection = new ReflectionClass($this);

        $sql = "select count(1) from " . $reflection->name;

        if ($where != "")
            $sql = $sql . " where " . $where;

        return $sql;
    }

    private function MontarSoma($campo, $where = "")
    {
        $reflection = new ReflectionClass($this);

        $sql = "select sum($campo) from " . $reflection->name;

        if ($where != "")
            $sql = $sql . " where " . $where;

        return $sql;
    }

    private function MontarDelete($where = "")
    {
        $reflection = new ReflectionClass($this);

        $sql = "delete from " . $reflection->name;

        if ($where != "")
            $sql = $sql . " where " . $where;

        return $sql;
    }

    public function ObterRegistrosDoBanco($sql)
    {
        include_once "mysqlexecuta.php";
        include "mysqlconecta.php";

        $registros = mysqlexecuta($id, $sql);

        return $registros;
    }

    public function ConverterRegistros($registros)
    {
        $reflection = new ReflectionClass($this);

        $entidades;
        while ($registro = mysql_fetch_array($registros))
        {
            $entidade = new $reflection->name();

            $indiceNumerico = false;

            foreach (array_keys($registro) as $coluna)
            {
                $indiceNumerico = !$indiceNumerico;
                if ($indiceNumerico)
                    continue;

                $entidade->$coluna = $registro[$coluna];
            }

            $entidades[] = $entidade;
        }

        if (isset($entidades))
            return $entidades;

        return NULL;
    }

    private function Insert($entidadeBase)
    {
        include_once "mysqlexecuta.php";
        include "mysqlconecta.php";

        $sql = $this->MontarInsert($entidadeBase);
        mysqlexecuta($id, $sql);

        $reflection = new ReflectionClass($entidadeBase);
        $propriedades = $this->getPropriedades($entidadeBase, $reflection);

        foreach ($propriedades as $propriedade)
        {
            $valor = $this->formatarCampo($entidadeBase->$propriedade);

            if ($valor == 'null')
                $valores[] = $propriedade . " is " . $valor;
            else
                $valores[] = $propriedade . " = " . $valor;
        }

        $where = implode(" and ", $valores);

        $entidadeAtualizada = $this->ObterPrimeiro($where);

        if ($entidadeAtualizada != NULL)
            $entidadeBase->Id = $entidadeAtualizada->Id;
    }

    public function MontarInsert($entidadeBase)
    {
        $reflection = new ReflectionClass($entidadeBase);
        $propriedades = $this->getPropriedades($entidadeBase, $reflection);
        $valores;

        include_once "mysqlexecuta.php";
        include "mysqlconecta.php";

        foreach ($propriedades as $propriedade)
        {
            $valores[] = $this->formatarCampo($entidadeBase->$propriedade);
        }

        $sql = "Insert into $reflection->name (" . implode(", ", $propriedades) . ") values (" . implode(", ", $valores) . ");";
        return $sql;
    }

    private function Update($entidadeBase)
    {
        include_once "mysqlexecuta.php";
        include "mysqlconecta.php";

        $sql = $this->MontarUpdate($entidadeBase);
        mysqlexecuta($id, $sql);
    }

    public function MontarUpdate($entidadeBase)
    {
        $reflection = new ReflectionClass($entidadeBase);
        $propriedades = $this->getPropriedades($entidadeBase, $reflection);
        $valores;

        include_once "mysqlexecuta.php";
        include "mysqlconecta.php";

        foreach ($propriedades as $propriedade)
        {
            $valores[] = $propriedade . " = " . $this->formatarCampo($entidadeBase->$propriedade);
        }
        $sql = "Update $reflection->name set " . implode(", ", $valores) . " where Id = $entidadeBase->Id";
        return $sql;
    }

    public function getPropriedades($entidadeBase, $reflect)
    {
        $propriedadesReflect = $reflect->getProperties(ReflectionProperty::IS_PUBLIC | ReflectionProperty::IS_PROTECTED);
        $propriedades;

        foreach ($propriedadesReflect as $propriedade)
        {
            $nome = $propriedade->getName();
            if ($nome == "Id")
                continue;

            $propriedades[] = $nome;
        }

        return $propriedades;
        ;
    }

    public function formatarCampo($obj)
    {
        switch (gettype($obj))
        {
            case "boolean":
                return $obj ? 1 : 0;
                break;

            case "integer":
                return $obj;
                break;

            case "double":
                return $obj;
                break;

            case "string":
                include_once "mysqlexecuta.php";
                return "'" . mysql_real_escape_string($obj) . "'";
                break;

            case "array":
                return "null";
                break;

            case "object":
                return "null";
                break;

            case "resource":
                return "null";
                break;

            case "NULL":
                return "null";
                break;
        }
        return "null";
    }

    function getCamposObrigatoriosInput()
    {
        return Array();
    }

    function getJavaScriptCamposObrigatoriosInput()
    {
        $campos = $this->getCamposObrigatoriosInput();

        foreach ($campos as $campo)
        {
            ?>
            if (form.<?php echo $campo ?>.value == "")
            {
            alert("Informe o Campo ".concat(form.<?php echo $campo ?>.placeholder));
            return false;
            }
            <?php
        }
    }

    function Converter($V)
    {
        foreach (array_keys($V) as $c)
        {
            $this->$c = $V[$c];
        }
    }

}
?>
